home *** CD-ROM | disk | FTP | other *** search
/ Amiga Tools 5 / Amiga Tools 5.iso / spiele / think / chinachallenge3 / c / cc3.c < prev    next >
C/C++ Source or Header  |  1995-11-02  |  11KB  |  494 lines

  1. /************************************************************************
  2. *                                    *
  3. * China Challenge III - the C Version                    *
  4. *                                    *
  5. * author    : Gunther Nikl                        *
  6. * created    : 8-may-94                        *
  7. * last change    : 2-nov-95                        *
  8. *                                    *
  9. ************************************************************************/
  10.  
  11. /* our include file */
  12.  
  13. #include "cc3.h"
  14.  
  15. /* init functions */
  16.  
  17. VOID InitMusic()
  18. {
  19.   ULONG rlen;
  20.   BPTR file;
  21.  
  22.   AudioPort.mp_Node.ln_Type=NT_MSGPORT;
  23.   if ((BYTE)(AudioPort.mp_SigBit=AllocSignal(-1L))>=0)
  24.   {
  25.     AudioPort.mp_SigTask=FindTask(NULL);
  26.     NEWLIST(&AudioPort.mp_MsgList);
  27.  
  28.     AudioIO.ioa_Request.io_Message.mn_Node.ln_Type=NT_MESSAGE;
  29.     AudioIO.ioa_Request.io_Message.mn_Node.ln_Pri=ADALLOC_MAXPREC;
  30.     AudioIO.ioa_Request.io_Message.mn_ReplyPort=&AudioPort;
  31.     AudioIO.ioa_Request.io_Flags=ADIOF_NOWAIT;
  32.     AudioIO.ioa_Data=ChannelMap;
  33.     AudioIO.ioa_Length=sizeof(ChannelMap);
  34.     if (!OpenDevice(AudioName,0,&AudioIO.ioa_Request,0))
  35.     {
  36.       AudioOpen++;
  37.       if ((SampleBuf=AllocMem(SAMPLESIZE,MEMF_CHIP|MEMF_PUBLIC)))
  38.       {
  39.         if ((file=Open(SampleName,MODE_OLDFILE)))
  40.         {
  41.           rlen=Read(file,SampleBuf,SAMPLESIZE);
  42.           Close(file);
  43.           if (rlen==SAMPLESIZE)
  44.           {
  45.             if (!(ciaa.ciapra & CIAF_LED))
  46.             {
  47.               ciaa.ciapra |= CIAF_LED; AudioOpen++;
  48.             }
  49.             OptMusic();
  50.             if (!AudioIO.ioa_Request.io_Error)
  51.               return;
  52.           }
  53.         }
  54.       }
  55.     }
  56.     FreeMusic();
  57.   }
  58.   MenuItems[7].Flags &= ~(CHECKED|ITEMENABLED|CHECKIT);
  59. }
  60.  
  61. LONG MakeGfx()
  62. {
  63.   PLANEPTR *planes;
  64.   int i;
  65.  
  66.   if ((ScrPtr=OpenScreen(&NewScreen)))
  67.   {
  68.     NewWindow.Screen=ScrPtr;
  69.     if ((WinPtr=OpenWindow(&NewWindow)))
  70.     {
  71.       SetMenuStrip(WinPtr,&MenuStrip[0]);
  72.       ShowTitle(ScrPtr,FALSE);
  73.       LoadRGB4(&ScrPtr->ViewPort,&ColorTab[0],1<<DEPTH);
  74.       InitRastPort(&RastPort);
  75.       SetFont(&RastPort,WinPtr->IFont);
  76.       InitBitMap(&BitMap,DEPTH,WIDTH,HEIGHT);
  77.       for (planes=&BitMap.Planes[0],i=DEPTH; i!=0 ; --i)
  78.        {
  79.          if (!(*planes++=AllocRaster(WIDTH,HEIGHT))) return;
  80.        }
  81.       RastPort.BitMap=&BitMap;
  82.       CurrentTime((ULONG *)&EntryTable[0],(ULONG *)&RandVal);
  83.       MakeDragon();
  84.       ScreenToFront(ScrPtr);
  85.       return 1;
  86.     }
  87.   }
  88.   /* return 0; */
  89. }
  90.  
  91. /* the main loop */
  92.  
  93. LONG Main()
  94. {
  95.   volatile struct IntuiMessage *imsg;
  96.   ULONG imClass;
  97.   UWORD imCode;
  98.  
  99.   if (MakeGfx())
  100.   {
  101.     InitMusic();
  102.     for (;;)
  103.      {
  104.        if (!(imsg=(struct IntuiMessage *)GetMsg(WinPtr->UserPort)))
  105.          WaitPort(WinPtr->UserPort);
  106.        else
  107.        {
  108.          imClass = imsg->Class; imCode  = imsg->Code;
  109.          ReplyMsg((struct Message *)imsg);
  110.          DoIDCMP(imClass,imCode);
  111.          if (EndAll)
  112.            break;
  113.        }
  114.      }
  115.   }
  116.   FreeMusic();
  117.   CloseGfx();
  118.   return (0);
  119. }
  120.  
  121. /* cleanup functions */
  122.  
  123. VOID CloseGfx()
  124. {
  125.   PLANEPTR *planes,p;
  126.   int i;
  127.  
  128.   for (planes=&BitMap.Planes[0],i=DEPTH; i!=0 ; i--)
  129.    {
  130.      if ((p=*planes++))
  131.        FreeRaster(p,WIDTH,HEIGHT);
  132.    }
  133.   if (WinPtr)
  134.   {
  135.     ClearMenuStrip(WinPtr); CloseWindow(WinPtr);
  136.   }
  137.   if (ScrPtr)
  138.     CloseScreen(ScrPtr);
  139. }
  140.  
  141. VOID FreeMusic()
  142. {
  143.   if (AudioOpen)
  144.     CloseDevice(&AudioIO.ioa_Request);
  145.   if ((BYTE)AudioPort.mp_SigBit>0)
  146.   {
  147.     FreeSignal(AudioPort.mp_SigBit); AudioPort.mp_SigBit=0;
  148.   }
  149.   if (SampleBuf)
  150.   {
  151.     FreeMem(SampleBuf,SAMPLESIZE); SampleBuf=NULL;
  152.     if (--AudioOpen)
  153.       ciaa.ciapra &= ~CIAF_LED;
  154.     AudioOpen=0;
  155.   }
  156. }
  157.  
  158. /* process all messages */
  159.  
  160. VOID DoIDCMP(ULONG imClass, ULONG imCode)
  161. {
  162.   LONG index,pos;
  163.  
  164.   if (imClass == MENUPICK)
  165.   {
  166.     ShowTitle(ScrPtr,FALSE);
  167.     for (;;)
  168.      {
  169.        SetAPen(&ScrPtr->RastPort,4);
  170.        Move(&ScrPtr->RastPort,0,0);
  171.        Draw(&ScrPtr->RastPort,WIDTH-1,0);
  172.        if ((UWORD)imCode == MENUNULL)
  173.          break;
  174.        switch (MENUNUM(imCode))
  175.        {
  176.          case 0: switch (ITEMNUM(imCode))
  177.                  {
  178.                    case 0: ProjectAbout(); break;
  179.                    case 1: EndAll=~0; break;
  180.                  }
  181.                  break;
  182.  
  183.          case 1: switch (ITEMNUM(imCode))
  184.                  {
  185.                    case 0: MakeDragon(); break;
  186.                    case 1: OptUndoMove(); break;
  187.                    case 2: OptUndoAll(); break;
  188.                    case 3: OptLoadDragon(); break;
  189.                    case 4: OptSaveDragon(); break;
  190.                    case 5: OptMusic(); break;
  191.                  }
  192.                  break;
  193.        }
  194.        imCode=(ULONG)(ItemAddress(&MenuStrip[0],imCode))->NextSelect;
  195.        if (EndAll)
  196.          break;
  197.      }
  198.   }
  199.   else
  200.     if ((imClass==MOUSEBUTTONS) && (imCode==IECODE_LBUTTON) && (pos=CheckPos())>=0)
  201.     {
  202.       if (TwoSelected && (PiecePos2 == pos || PiecePos1 == pos))
  203.       {
  204.         index=(MAXCOUNT-PieceCount)/2; PieceCount-=2;
  205.         NewDragon.PieceTable[PiecePos1] |= 0x80; NewDragon.UndoTable[index].pos1 = PiecePos1;
  206.         NewDragon.PieceTable[PiecePos2] |= 0x80; NewDragon.UndoTable[index].pos2 = PiecePos2;
  207.         ShowDragon();
  208.       }
  209.       else
  210.       {
  211.         if (OnePiece)
  212.         {
  213.           if (PiecePos1==pos)
  214.             return;
  215.           if (NewDragon.PieceTable[PiecePos1]==NewDragon.PieceTable[pos])
  216.           {
  217.             TwoSelected=1; PiecePos2=pos;
  218.           }
  219.           else
  220.           {
  221.             OnePiece=1; PiecePos1=pos;
  222.           }
  223.         }
  224.         else
  225.         {
  226.           OnePiece=1; PiecePos1=pos;
  227.         }
  228.         DrawImage(WinPtr->RPort,&Images[NewDragon.PieceTable[pos]],(TwoSelected ? 291:3),85);
  229.       }
  230.     }
  231. }
  232.  
  233. /* project function(s) */
  234.  
  235. VOID ProjectAbout()
  236. {
  237.   struct Window *wptr;
  238.   struct RastPort *rp;
  239.   struct About *p;
  240.   int i,j;
  241.  
  242.   AboutWindow.Screen=ScrPtr;
  243.   if ((wptr=OpenWindow(&AboutWindow)))
  244.   {
  245.     rp=wptr->RPort;
  246.     SetRast(rp,5); SetBPen(rp,5);
  247.     for (i=2; i!=0; i--)
  248.      { for (p=&About[0],j=9; j!=0; p++,j--)
  249.         {
  250.           SetAPen(rp,p->pens[i-1]); Move(rp,p->x+i-1,p->y+i-1); Text(rp,&p->text[0],23);
  251.         }
  252.        SetDrMd(rp,JAM1);
  253.      }
  254.     for (i=2; i!=0; i--)
  255.       DrawImage(rp,&Images[Random(30)+1],(i==2 ? 2:168),23);
  256.     WaitPort(wptr->UserPort);
  257.     CloseWindow(wptr);
  258.   }
  259. }
  260.  
  261. /* option functions */
  262.  
  263. VOID OptUndoMove()
  264. {
  265.   LONG index;
  266.  
  267.   if ((index=(MAXCOUNT-PieceCount)/2-1)>=0)
  268.   {
  269.     PieceCount+=2;
  270.     NewDragon.PieceTable[NewDragon.UndoTable[index].pos1] &= 0x7f;
  271.     NewDragon.PieceTable[NewDragon.UndoTable[index].pos2] &= 0x7f;
  272.     ShowDragon();
  273.   }
  274. }
  275.  
  276. VOID OptUndoAll()
  277. {
  278.   char *p;
  279.   short i;
  280.  
  281.   if (PieceCount!=MAXCOUNT)
  282.   {
  283.     PieceCount=MAXCOUNT;
  284.     for (p=&NewDragon.PieceTable[0],i=288; i!=0; *p++ &= 0x7f,i--) ;
  285.     ShowDragon();
  286.   }
  287. }
  288.  
  289. VOID OptLoadDragon()
  290. {
  291.   WORD header[2];
  292.   BPTR file;
  293.  
  294.   if ((file=ReqFile(0)))
  295.   {
  296.     Read(file,(APTR)&header[0],sizeof(header));
  297.     if (header[0]==0x4333)
  298.     {
  299.       PieceCount=header[1];
  300.       Read(file,&NewDragon,sizeof(struct Dragon));
  301.       ShowDragon();
  302.     }
  303.     Close(file);
  304.   }
  305. }
  306.  
  307. VOID OptSaveDragon()
  308. {
  309.   WORD header[2];
  310.   BPTR file;
  311.  
  312.   if ((file=ReqFile(1)))
  313.   {
  314.     header[0]=0x4333; header[1]=PieceCount;
  315.     Write(file,(APTR)&header[0],sizeof(header));
  316.     Write(file,&NewDragon,sizeof(struct Dragon));
  317.     Close(file);
  318.   }
  319. }
  320.  
  321. VOID OptMusic()
  322. {
  323.   struct IOAudio *areq;
  324.    BYTE OnOff;
  325.   UWORD cmd;
  326.  
  327.   if (AudioOpen)
  328.   {
  329.     OnOff=(MenuItems[7].Flags&CHECKED?~0:0);
  330.     if (Music!=OnOff)
  331.     {
  332.       areq=&AudioIO;
  333.       cmd=ADCMD_FINISH;
  334.       if (OnOff)
  335.       {
  336.         areq->ioa_Request.io_Flags=IOF_QUICK|ADIOF_PERVOL;
  337.         areq->ioa_Data=SampleBuf+104L;
  338.         areq->ioa_Length=2*51984;
  339.         areq->ioa_Period=428;
  340.         areq->ioa_Volume=55;
  341.         areq->ioa_Cycles=0;
  342.         cmd=CMD_WRITE;
  343.       }
  344.       areq->ioa_Request.io_Command=cmd;
  345.       BeginIO(&areq->ioa_Request);
  346.       Music=~Music;
  347.     }
  348.   }
  349. }
  350.  
  351. /* mouseclick valid ? */
  352.  
  353. LONG CheckPos()
  354. {
  355.   unsigned int x,y,z,d;
  356.   int i;
  357.  
  358.   for (d=1,i=3; i>=0; d+=3,i--)
  359.    {
  360.      if ( ((y=(WinPtr->MouseY-d)/30)<6) && ((x=(WinPtr->MouseX-d)/25)<12)
  361.           && (NewDragon.PieceTable[z=(6*12*i+12*y+x)]>0) )
  362.      {
  363.        if ( x==0 || x==11 || ((NewDragon.PieceTable[z-1]<=0 || NewDragon.PieceTable[z+1]<=0)
  364.             && (i==3 || NewDragon.PieceTable[12*6+z]<=0)))
  365.        {
  366.          return z;
  367.        }
  368.        break;
  369.      }
  370.    }
  371.   return -1;
  372. }
  373.  
  374. /* create a new dragon */
  375.  
  376. VOID MakeDragon()
  377. {
  378.   int i,j,k,l,pos;
  379.   UBYTE *p1,*p2;
  380.  
  381.   PieceCount=MAXCOUNT;
  382.  
  383.   for (p1=p2=&EntryTable[0],i=MAXCOUNT/4; i!=0; i--)
  384.    {
  385.      *p1++=i; *p1++=i; *p1++=i; *p1++=i;
  386.    }
  387.   for (p1=&NewDragon.PieceTable[0],j=-1,i=MAXCOUNT; i!=0; i--)
  388.    {
  389.      do
  390.      {
  391.       j++; k=(-8)&j; l=j-k; k=k>>3;
  392.      } while (!(PosTable[k]&1<<l));
  393.      pos=Random(i); p1[j]=p2[pos]; p2[pos]=p2[i-1];
  394.    }
  395.   ShowDragon();
  396. }
  397.  
  398. /* random number generator */
  399.  
  400. LONG Random(ULONG Num)
  401. {
  402.   ULONG i,j;
  403.  
  404.   i=RandVal; j=i>>12; i^=j; j=i<<20; i^=j; RandVal=i; return (i%Num);
  405. }
  406.  
  407. /* draw the dragon */
  408.  
  409. VOID ShowDragon()
  410. {
  411.   ULONG *p1;
  412.   BYTE *p2;
  413.   short n;
  414.   int i,j,k,x,y,d;
  415.  
  416.   TwoSelected=OnePiece=0;
  417.  
  418.   for (p1=&BackGroundTab[0],i=4; i!=0; i--)
  419.    {
  420.      DrawImage(&RastPort,&Images[0],p1[0],p1[1]); p1++; p1++;
  421.    }
  422.   DrawBorder(&RastPort,&Border[0],0,0);
  423.   for (p2=&NewDragon.PieceTable[0],d=10,i=4; i!=0; d-=3,i--)
  424.     for (y=0,j=6; j!=0; y+=30,j--)
  425.       for (x=0,k=12; k!=0; x+=25,k--)
  426.         if ((n=*p2++)>0)
  427.           DrawImage(&RastPort,&Images[n],x+d,y+d);
  428.   PrintPieces();
  429.   BltBitMapRastPort(&BitMap,0,0,WinPtr->RPort,0,0,WIDTH,HEIGHT-2,0xc0);
  430. }
  431.  
  432. /* print remaining pieces */
  433.  
  434. VOID PrintPieces()
  435. {
  436.   int i;
  437.  
  438.   for (i=3; i!=0; i--)
  439.    {
  440.      SetAPen(&RastPort,APenTab[i]);
  441.      RectFill(&RastPort,278-i,51-i,312+i,60+i);
  442.    }
  443.   sprintf(BlankStr,PieceFmt,PieceCount);
  444.   PrintIText(&RastPort,&MoveIText,0,0);
  445. }
  446.  
  447. /* select a file and open the file for read or write */
  448.  
  449. BPTR ReqFile(LONG Type)
  450. {
  451.   struct Library *ArpBase;
  452.   struct ChinaReq *req;
  453.   APTR oldwin,*wptr;
  454.   BPTR file=0;
  455.  
  456.   wptr=&((struct Process *)FindTask(NULL))->pr_WindowPtr;
  457.   oldwin=*wptr; *wptr=WinPtr; WinPtr->Flags |= RMBTRAP;
  458.   if ((req=(struct ChinaReq *)AllocMem(sizeof(struct ChinaReq),MEMF_CLEAR)))
  459.   {
  460.     if ((ArpBase=OpenLibrary(ArpName,39L)))
  461.     {
  462.       req->FReq.fr_Hail   = (!Type ? LoadDragonStr : SaveDragonStr);
  463.       req->FReq.fr_File   = &req->FileBuf;
  464.       req->FReq.fr_Dir    = &req->DirBuf;
  465.       req->FReq.fr_Window = WinPtr;
  466.       req->FReq.fr_Flags  = 0x28; /* DoColor && NewWindFunc */
  467.       req->FReq.fr_res1   = 1; /* LongPath */ 
  468.       req->FReq.fr_Func   = (VOID (*)())ChangeFunc;
  469.       if (FileRequest(ArpBase,&req->FReq))
  470.       {
  471.         TackOn(ArpBase,&req->DirBuf[0],&req->FileBuf[0]);
  472.         file=ArpOpen(ArpBase,&req->DirBuf[0],MODE_OLDFILE+Type);
  473.       }
  474.       CloseLibrary(ArpBase);
  475.     }
  476.     FreeMem((APTR)req,sizeof(struct ChinaReq));
  477.   }
  478.   WinPtr->Flags &= ~RMBTRAP; *wptr=oldwin;
  479.   return file;
  480. }
  481.  
  482. VOID ChangeFunc()
  483. {
  484.   register struct NewWindow *new asm("a0");
  485.  
  486.   new->LeftEdge=10; new->TopEdge=10;
  487. }
  488.  
  489. /************************************************************************
  490. *                                    *
  491. * end of China Challenge III - the C Version                *
  492. *                                    *
  493. ************************************************************************/
  494.